home *** CD-ROM | disk | FTP | other *** search
/ PCMania 44 / PCMania CD44_1.iso / pcmania / mod44 / mix.c < prev    next >
C/C++ Source or Header  |  1994-03-05  |  6KB  |  264 lines

  1.  
  2. //    *** ------------------------------------- ***
  3. //    *        Smp-Player , programado por        *
  4. //    *           Esteban Moreno Valdés           *
  5. //    *   ( Colaborador de la revista Pcmanía )   *
  6. //    *** ------------------------------------- ***
  7.  
  8. #include <stdio.h>
  9. #include <conio.h>
  10. #include <alloc.h>
  11. #include <dos.h>
  12. #include <process.h>
  13. #include <fcntl.h>
  14. #include <io.h>
  15.  
  16. #define BYTE unsigned char
  17. #define WORD unsigned  int
  18.  
  19. BYTE far *data;
  20. BYTE far *data2;
  21.  
  22. WORD constant=1,len,len2,freq,number,counter=0;
  23. WORD RESET_PORT= 0x216;
  24. WORD WRITE_PORT= 0x21C;
  25. WORD READD_PORT= 0x21A;
  26. WORD READS_PORT= 0x21E;
  27.  
  28. void sb_detect(void);               // ¡¿¡ Está claro !?!
  29. void load_info(char fichero[],char fichero2[]); // Carga el sample en memoria
  30. void set_video_mode(BYTE);          // Establece modo de pantalla especificado
  31. void fin(void);                     // Muestra los creditos
  32. void interrupt newint8(void);       // Nuevo vector de interrupción
  33. void interrupt (*oldint8)(void);    // Antiguo vector de interrupción
  34. void set_timer(void);               // Establece nueva frecuencia
  35. void res_timer(void);               // Restaura antigua frecuencia
  36. void write_dsp(BYTE);
  37. void wait_dsp(void);
  38.  
  39. void main(int argc,char *argv[])
  40. {
  41.     if (argc<3) {
  42.              clrscr();
  43.              fin();
  44.              printf("Error    : Falta parámetro requerido.");
  45.              printf("\nSintaxis : MIX.EXE VOL1 FILE1.EXT VOL2 FILE2.EXT\n");
  46.              exit(0);
  47.              };
  48.  
  49.     set_video_mode(0x03);
  50.     sb_detect();
  51.     load_info(argv[1],argv[2]);
  52.     freq=14000;
  53.     number = (WORD)(1193180l/freq);
  54.     set_timer();
  55.     write_dsp(0xD1);
  56.     oldint8=getvect(8);
  57.     setvect(8,newint8);
  58.  
  59.     for(;constant<=len;) { }
  60.  
  61.     write_dsp(0xD3);
  62.     res_timer();
  63.     setvect(8,oldint8);         // Restauramos el vector de interrupción
  64.     farfree(data);              // Liberamos la memoria utilizada
  65.     farfree(data2);
  66. }
  67.  
  68. void load_info(char fichero[],char fichero2[])
  69. {
  70.     int handle,handle2;
  71.     WORD n;
  72.     unsigned bytes_read,bytes_read2;
  73.  
  74.     // Carga el primer y segundo sample en memoria
  75.  
  76.     if ((_dos_open(fichero,O_RDONLY,&handle))!=0) {
  77.         printf(" Error : Fichero no encontrado : %s\n",fichero);
  78.         exit(0);
  79.     }
  80.     if ((_dos_open(fichero2,O_RDONLY,&handle2))!=0) {
  81.         printf(" Error : Fichero no encontrado : %s\n",fichero2);
  82.         exit(0);
  83.     }
  84.  
  85.     len = (WORD)filelength(handle);
  86.     len2 = (WORD)filelength(handle2);
  87.  
  88.     if (len<len2) { len=len2; }
  89.  
  90.     if ( (data=(BYTE far*)farmalloc(len))==NULL) {
  91.         printf(" Error : No se puede asignar memoria correctamente.\n");
  92.         exit(0);
  93.     }
  94.     if ( (data2=(BYTE far*)farmalloc(len))==NULL) {
  95.         printf(" Error : No se puede asignar memoria correctamente.\n");
  96.         exit(0);
  97.     }
  98.  
  99.     for (n=0;n<=len;n++) { *(data+n)=0; *(data2+n)=0; }
  100.  
  101.     _dos_read(handle,(BYTE far*)data,len,&bytes_read);
  102.     _dos_close(handle);
  103.     _dos_read(handle2,(BYTE far*)data2,len2,&bytes_read2);
  104.     _dos_close(handle2);
  105.  
  106.     printf("Mixing : %12s = %u\n",fichero,len);
  107.     printf("         %12s = %u\n\n",fichero2,len2);
  108. }
  109.  
  110. void sb_detect(void)
  111. {
  112.     BYTE valor=0;
  113.     WORD counter=1;
  114.  
  115.     while (!valor) {
  116.  
  117.     outportb(RESET_PORT,1);
  118.     delay(3);                             // Esperamos 3 milisegundos
  119.     outportb(RESET_PORT,0);
  120.                           // Esperamos la disponibilidad
  121.                           // de un byte en el puerto de
  122.                           // datos
  123.  
  124.     while (!(inportb(READS_PORT) & 128) || counter>=0xFFFF) counter++;
  125.  
  126.     if (inportb(READD_PORT)!=0xAA) {
  127.  
  128.         RESET_PORT+=0x10;
  129.         WRITE_PORT+=0x10;
  130.         READD_PORT+=0x10;
  131.         READS_PORT+=0x10;
  132.  
  133.          if (RESET_PORT>=0x270) { valor=1;
  134.                       fin();
  135.                       printf("     No se ha detectado una tarjeta\n");
  136.                       printf("     Sound-Blaster o compatible.\n\n");
  137.          }
  138.     }
  139.         else { valor=1;
  140.            fin();
  141.            printf(" ¡ Felicidades ! Se ha detectado una tarjeta\n");
  142.            printf(" SOUND_BLASTER o compatible, instalada en la\n");
  143.            printf(" Direcc. Puerto Base %Xh.\n\n",RESET_PORT-0x06);
  144.         }
  145.     }
  146. }
  147.  
  148. void set_video_mode(BYTE mode)
  149. {
  150.     asm {
  151.         xor    ah,ah
  152.         mov    al,mode
  153.         int    10h
  154.     }
  155. }
  156.  
  157.  
  158. void fin(void)
  159. {
  160.            printf("╔════════════════════════════════════════╗\n");
  161.            printf("║           · Smp-Mix-Player ·           ║\n");
  162.            printf("║  Programado por Esteban Moreno Valdés  ║\n");
  163.            printf("║        para la revista Pcmanía         ║\n");
  164.            printf("╚════════════════════════════════════════╝\n\n");
  165. }
  166.  
  167. void set_timer(void)
  168. {
  169.     outportb(0x43,54);
  170.     outportb(0x40,(number & 0x00FF));        // Byte bajo
  171.     outportb(0x40,(number & 0xFF00)>>8);     // Byte alto
  172. }
  173.  
  174. void res_timer(void)
  175. {
  176.     outportb(0x43,0x36);       // Frecuencia del timer : 1193180
  177.     outportb(0x40,0);          // Byte bajo
  178.     outportb(0x40,0);          // Byte alto
  179. }
  180.  
  181. void interrupt newint8(void)
  182. {
  183.  
  184.     WORD segment,offs,segment2,offs2;
  185.  
  186.     segment=FP_SEG(data);
  187.        offs=FP_OFF(data);
  188.     segment2=FP_SEG(data2);
  189.        offs2=FP_OFF(data2);
  190.  
  191.     asm {
  192.         call    far ptr wait_dsp
  193.  
  194.         mov    al,10h
  195.         out    dx,al             // Modo directo
  196.  
  197.         call    far ptr wait_dsp
  198.  
  199.         push    ds
  200.         push    es
  201.         mov    ax,segment
  202.         mov    ds,ax
  203.         mov    si,offs
  204.         mov    ax,segment2
  205.         mov    es,ax
  206.         mov    di,offs2
  207.  
  208.         xor    ax,ax
  209.         xor    bx,bx
  210.         xor    cx,cx
  211.  
  212.         mov    bl,[si]           // Byte del primer instrumento
  213.         mov    cl,es:[di]        // Byte del segundo instrumento
  214.         pop    es
  215.         pop    ds
  216.         add    bl,128            // Incluid esta líneas para las
  217.         add    cl,128            // muestras con signo
  218.         add    ax,bx
  219.         add    ax,cx
  220.         shr    ax,1
  221.  
  222.         out    dx,al
  223.  
  224.         mov    ax,number
  225.         add    counter,ax
  226.         jnc    B1
  227.  
  228.     }
  229.         oldint8();
  230.    B1:;
  231.     asm {
  232.         mov    dx,20h
  233.         mov    al,20h
  234.         out    dx,al             // Fin de interrupción de hardware
  235.      }
  236.         constant++;
  237.         data++;                   // Incrementamos la dirección de
  238.         data2++;                  // los dos punteros
  239. }
  240.  
  241.  
  242. void write_dsp(BYTE dato)
  243. {
  244.      asm    push    ax
  245.      asm     mov    dx,WRITE_PORT
  246.  bucle:;
  247.      asm    in    al,dx
  248.      asm    test    al,10000000b
  249.      asm    jnz    bucle
  250.      asm    mov    al,dato
  251.      asm    out    dx,al
  252.      asm    pop    ax
  253. }
  254.  
  255. void wait_dsp(void)
  256. {
  257.      asm    push    ax
  258.      asm     mov    dx,WRITE_PORT
  259.  bucle:;
  260.      asm    in    al,dx
  261.      asm    test    al,10000000b
  262.      asm    jnz    bucle
  263.      asm    pop    ax
  264. }